using UnityEditor;
using UnityEngine;
using System.IO;
using System.Collections.Generic;
using System.Linq;
using TMPro;

//// <summary>
/// 高级资源包打包工具，在project窗口中选择需要打包的资源，然后点击开始构建即可
/// </summary>
public class AssetBundleBuilder : EditorWindow
{
    private enum BuildMode { 单独打包, 合并打包 }
    private enum CompressionType { None, LZMA, LZ4 }

    [MenuItem("工具/AssetBundle打包工具")]
    public static void ShowWindow()
    {
        GetWindow<AssetBundleBuilder>("AssetBundle打包工具");
    }

    // 配置参数
    private BuildTarget buildTarget = BuildTarget.StandaloneWindows;
    private CompressionType compressionType = CompressionType.LZ4;
    private string outputPath = "Assets/AssetBundles";
    private BuildMode buildMode = BuildMode.单独打包;
    private string combinedBundleName = "合并资源包";
    private string bundleVersion = "1.0.0";

    // 高级选项
    private bool disableWriteTypeTree = false;
    private bool forceRebuild = false;
    private bool ignoreTypeTreeChanges = false;
    private bool appendHash = false;
    private bool strictMode = true;
    private bool needBundleVersion = false;

    private void OnGUI()
    {
        GUILayout.Label("高级资源包打包工具", EditorStyles.boldLabel);

        // 构建模式选择
        buildMode = (BuildMode)EditorGUILayout.EnumPopup("打包模式", buildMode);

        if (buildMode == BuildMode.合并打包)
        {
            combinedBundleName = EditorGUILayout.TextField("包体名称", combinedBundleName);
        }

        // 平台选择
        buildTarget = (BuildTarget)EditorGUILayout.EnumPopup("目标平台", buildTarget);

        // 压缩选项分组
        EditorGUILayout.Space();
        GUILayout.Label("压缩设置", EditorStyles.boldLabel);
        compressionType = (CompressionType)EditorGUILayout.EnumPopup("压缩算法", compressionType);

        // 高级构建选项
        EditorGUILayout.Space();
        GUILayout.Label("高级选项", EditorStyles.boldLabel);
        disableWriteTypeTree = EditorGUILayout.Toggle("禁用类型树", disableWriteTypeTree);
        appendHash = EditorGUILayout.Toggle("附加哈希值", appendHash);
        forceRebuild = EditorGUILayout.Toggle("强制重建", forceRebuild);
        ignoreTypeTreeChanges = EditorGUILayout.Toggle("忽略类型变化", ignoreTypeTreeChanges);
        strictMode = EditorGUILayout.Toggle("严格模式", strictMode);
        needBundleVersion = EditorGUILayout.Toggle("在包名后加版本号", needBundleVersion);

        if (needBundleVersion)
        {
            // 扩展功能
            EditorGUILayout.Space();
            GUILayout.Label("版本控制", EditorStyles.boldLabel);
            bundleVersion = EditorGUILayout.TextField("版本号", bundleVersion);
        }

        // 输出路径
        EditorGUILayout.Space();
        outputPath = EditorGUILayout.TextField("输出路径", outputPath);

        // 操作按钮
        EditorGUILayout.Space(20);
        EditorGUILayout.BeginHorizontal();
        if (GUILayout.Button("开始构建", GUILayout.Height(30)))
        {
            if (Selection.objects.Length == 0)
            {
                EditorUtility.DisplayDialog("错误", "请在项目窗口中选择资源！", "确定");
                return;
            }
            BuildAssetBundles();
        }
        if (GUILayout.Button("清理缓存", GUILayout.Height(30)))
        {
            CleanAssetBundles();
        }
        EditorGUILayout.EndHorizontal();

        // 状态信息
        EditorGUILayout.HelpBox(
            $"当前选中：{Selection.objects.Length} 个资源\n" +
            $"打包模式：{buildMode}\n" +
            $"目标平台：{buildTarget}\n" +
            $"压缩设置：{GetCompressionDescription()}",
            MessageType.Info);
    }

    private string GetCompressionDescription()
    {
        var desc = new List<string>();
        desc.Add(compressionType.ToString());
        if (disableWriteTypeTree) desc.Add("禁用类型树");
        if (appendHash) desc.Add("带哈希值");
        return string.Join(" + ", desc);
    }

    private void BuildAssetBundles()
    {
        try
        {
            // 获取有效资源路径
            var assetPaths = GetSelectedAssetPaths();
            if (assetPaths.Count == 0)
            {
                EditorUtility.DisplayDialog("错误", "未找到有效资源！", "确定");
                return;
            }

            // 准备输出目录
            if (!Directory.Exists(outputPath))
            {
                Directory.CreateDirectory(outputPath);
            }

            // 设置资源包属性
            SetAssetBundleNames(assetPaths);

            // 构建选项配置
            BuildAssetBundleOptions options = BuildAssetBundleOptions.None;

            // 设置压缩算法
            switch (compressionType)
            {
                case CompressionType.LZMA:
                    options |= BuildAssetBundleOptions.None; // LZMA是默认值
                    break;
                case CompressionType.LZ4:
                    options |= BuildAssetBundleOptions.ChunkBasedCompression;
                    break;
                case CompressionType.None:
                    options |= BuildAssetBundleOptions.UncompressedAssetBundle;
                    break;
            }

            // 添加其他选项
            if (disableWriteTypeTree) options |= BuildAssetBundleOptions.DisableWriteTypeTree;
            if (forceRebuild) options |= BuildAssetBundleOptions.ForceRebuildAssetBundle;
            if (ignoreTypeTreeChanges) options |= BuildAssetBundleOptions.IgnoreTypeTreeChanges;
            if (appendHash) options |= BuildAssetBundleOptions.AppendHashToAssetBundleName;
            if (strictMode) options |= BuildAssetBundleOptions.StrictMode;

            // 执行打包操作
            BuildPipeline.BuildAssetBundles(
                outputPath,
                options,
                buildTarget
            );

            // 后处理
            ResetAssetBundleNames(assetPaths);
            AssetDatabase.Refresh();
            EditorUtility.DisplayDialog("完成", $"资源包构建成功！\n输出路径：{outputPath}", "确定");
        }
        catch (System.Exception e)
        {
            EditorUtility.DisplayDialog("错误", $"构建失败：{e.Message}", "确定");
        }
    }

    // 获取选中资源的有效路径
    private List<string> GetSelectedAssetPaths()
    {
        var paths = new List<string>();
        foreach (var obj in Selection.objects)
        {
            var path = AssetDatabase.GetAssetPath(obj);
            if (string.IsNullOrEmpty(path)) continue;

            if (Directory.Exists(path))
            {
                // 递归获取文件夹内容
                var files = Directory.GetFiles(path, "*", SearchOption.AllDirectories)
                    .Where(p => !IsMetaFile(p))
                    .ToArray();
                paths.AddRange(files);
            }
            else
            {
                // 添加单个文件
                if (!IsMetaFile(path))
                {
                    paths.Add(path);
                }
            }
        }
        return paths.Distinct().ToList();
    }

    // 判断是否为元文件
    private bool IsMetaFile(string path)
    {
        return path.EndsWith(".meta") || path.EndsWith(".DS_Store");
    }

    // 设置资源包名称（带版本号）
    private void SetAssetBundleNames(List<string> assetPaths)
    {
        foreach (var path in assetPaths)
        {
            var importer = AssetImporter.GetAtPath(path);
            if (importer == null) continue;

            var baseName = buildMode == BuildMode.单独打包 ?
                Path.GetFileNameWithoutExtension(path) :
                combinedBundleName;

            // 添加版本号后缀
            if (needBundleVersion)
            {
                importer.assetBundleName = $"{baseName}_v{bundleVersion}".ToLower();
            }
            else
            {
                importer.assetBundleName = baseName.ToLower();
            }
        }
    }

    // 重置资源包设置
    private void ResetAssetBundleNames(List<string> assetPaths)
    {
        foreach (var path in assetPaths)
        {
            var importer = AssetImporter.GetAtPath(path);
            if (importer != null)
            {
                importer.assetBundleName = null;
            }
        }
    }

    // 清理输出目录
    private void CleanAssetBundles()
    {
        if (Directory.Exists(outputPath))
        {
            Directory.Delete(outputPath, true);
            File.Delete($"{outputPath}.meta");
            AssetDatabase.Refresh();
            EditorUtility.DisplayDialog("提示", "已清理所有资源包！", "确定");
        }
    }
}